<?php

namespace App\Http\Validate\Kms\Auth;

use App\Http\Validate\AbstractBaseValidate;
use App\Models\Kms\User\KmsUser;
use Illuminate\Support\Facades\Validator;
use Illuminate\Support\MessageBag;
use Illuminate\Validation\Rule;
use Illuminate\Validation\ValidationException;
use Laravel\Passport\Client;
use Laravel\Passport\Passport;
use Psr\Container\ContainerExceptionInterface;
use Psr\Container\NotFoundExceptionInterface;

class AuthValidate extends AbstractBaseValidate
{
    function getRules(): array
    {
        // TODO: Implement getRules() method.
        return [];
    }

    function getAttributes(): array
    {
        // TODO: Implement getAttributes() method.
        return [];
    }

    function registerValidateRules(): void
    {
        // TODO: Implement registerValidateRules() method.
        Validator::extend('mobile', function ($attribute, $value, $parameters, $validator) {
            return $validator->validateRegex(
                $attribute,
                $value,
                ['/^1\d{10}$/'],
                "手机号格式非法"
            );
        });
    }

    function getMessages(): array
    {
        // TODO: Implement getMessages() method.
        return [];
    }

    /**
     * @param array $params
     * @return MessageBag|object
     * @throws ValidationException
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public static function fsLoginValidate(array $params)
    {
        $versionCompareRes = version_compare($params["appVersion"] ?? 0, "1.1.2", ">");
        return self::getInstance()->validate(
            [
                "code",
                "appVersion",
                "longitude",
                "latitude",
                "deviceModel",
                "deviceSystem",
                "deviceSerialNumber",
                "userAgent"
            ],
            $params,
            [
                "code"               => self::stringValidateBuild(true, 72, 1),
                "appVersion"         => [
                    "required",
                    "string",
                    "regex:/^[1-9][\d]*+[\.\d+]{1,10}$/"
                ],
                "userAgent"          => "string",
                "longitude"          => Rule::when(
                    $versionCompareRes,
                    [
                        "string"
                    ],
                    [
                        "string",
                        "regex:/^[\-\+]?(0?\d{1,2}(\.\d{1,6})*|1[0-7]?\d{1}(\.\d{1,6})*|180(\.0{1,6})*)$/"
                    ]
                ),
                "latitude"           => Rule::when(
                    $versionCompareRes,
                    [
                        "string"
                    ],
                    [
                        "string",
                        "regex:/^[\-\+]?([0-8]?\d{1}(\.\d{1,6})*|90(\.0{1,6})*)$/"
                    ]
                ),
                "deviceSystem"       => Rule::when($versionCompareRes,
                    [
                        "required",
                        "string",
                        "max:64"
                    ],
                    "string"
                ),
                "deviceSerialNumber" => Rule::when($versionCompareRes,
                    [
                        "required",
                        "string",
                        "max:120"
                    ],
                    "string"
                ),
                "deviceModel"        => Rule::when($versionCompareRes,
                    [
                        "required",
                        "string",
                        "max:64"
                    ],
                    "string"
                ),
            ]
        );
    }

    /**
     * @param array $params
     * @return MessageBag|object
     * @throws ValidationException
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public static function virtualLoginValidate(array $params)
    {
        $versionCompareRes = version_compare($params["appVersion"] ?? 0, "1.1.2", ">");
        return self::getInstance()->validate(
            [
                "mobile",
                "password",
                "appVersion",
                "longitude",
                "latitude",
                "deviceModel",
                "deviceSystem",
                "deviceSerialNumber",
                "userAgent"
            ],
            $params,
            [
                "mobile"             => [
                    "required",
                    "string",
                    "size:11",
                    "mobile",
                    Rule::exists((new KmsUser())->getTable(), "mobile")
                ],
                "password"           => "required|string|min:6|max:18",
                "appVersion"         => [
                    "required",
                    "string",
                    "regex:/^[1-9][\d]*+[\.\d+]{1,10}$/"
                ],
                "userAgent"          => "string",
                "longitude"          => Rule::when(
                    $versionCompareRes,
                    [
                        "required",
                        "string"
                    ],
                    [
                        "string",
                        "regex:/^[\-\+]?(0?\d{1,2}(\.\d{1,6})*|1[0-7]?\d{1}(\.\d{1,6})*|180(\.0{1,6})*)$/"
                    ]
                ),
                "latitude"           => Rule::when(
                    $versionCompareRes,
                    [
                        "required",
                        "string"
                    ],
                    [
                        "string",
                        "regex:/^[\-\+]?([0-8]?\d{1}(\.\d{1,6})*|90(\.0{1,6})*)$/"
                    ]
                ),
                "deviceSystem"       => Rule::when($versionCompareRes,
                    [
                        "required",
                        "string",
                        "max:64"
                    ],
                    "string"
                ),
                "deviceSerialNumber" => Rule::when($versionCompareRes,
                    [
                        "required",
                        "string",
                        "max:120"
                    ],
                    "string"
                ),
                "deviceModel"        => Rule::when($versionCompareRes,
                    [
                        "required",
                        "string",
                        "max:64"
                    ],
                    "string"
                ),
            ]
        );
    }

    /**
     * @param array $params
     * @return MessageBag|object
     * @throws ValidationException
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public static function codeValidate(array $params)
    {
        return self::getInstance()->validate(
            ["clientId"],
            $params,
            [
                "clientId" => [
                    "required",
                    "int",
                    Rule::exists((new Client())->getTable(), "id")
                ]
            ]
        );
    }


    /**
     * @param array $params
     * @return MessageBag|object
     * @throws ValidationException
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public static function callbackValidate(array $params)
    {
        return self::getInstance()->validate(
            ["code", "state"],
            $params,
            [
                "code"  => self::stringValidateBuild(true, 10000, 1),
                "state" => self::stringValidateBuild(true, 10000, 1)
            ]
        );
    }


    /**
     * @param array $params
     * @return MessageBag|object
     * @throws ValidationException
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     */
    public static function tokenValidate(array $params)
    {
        return self::getInstance()->validate(
            ["code", "clientId"],
            $params,
            [
                "code"     => self::stringValidateBuild(true, 10000, 1),
                "clientId" => [
                    "required",
                    "int",
                    Rule::exists((new Client())->getTable(), "id")
                ]
            ]
        );
    }

    /**
     * @param array $params
     * @return MessageBag|object
     * @throws ContainerExceptionInterface
     * @throws NotFoundExceptionInterface
     * @throws ValidationException
     */
    public static function authorizeValidate(array $params)
    {
        return self::getInstance()->validate(
            ["client_id"],
            $params,
            [
                "client_id" => [
                    "required",
                    "int",
                    Rule::exists((new Client())->getTable(), "id")
                ]
            ]
        );
    }
}
